# -*- coding: utf-8 -*-
# @Time    : 2020/4/7 10:07
# @Author  : ZSQ
# @Email   : zsq199170918@163.com
# @FileName: case_to_html.py
# @Software: PyCharm
import re
import os
import sys
import datetime
from functools import reduce
from pymongo import MongoClient
from FDC_spider.utils.digit_to_rmb import DigitToRmb
from concurrent.futures import ThreadPoolExecutor, wait
from FDC_spider.constants import TR_GET_STR, TR_OUT_STR

HOST = '127.0.0.1'
PORT = 27017
EXECUTOR = ThreadPoolExecutor(max_workers=6)  # 线程池，最多6个线程


def auction_notice(case, func_li):
    """
    竞买/应买公告
    :param case: 案例对象
    :param func_li: 函数名列表
    :return: None
    """
    func_name = sys._getframe().f_code.co_name
    if func_name in func_li:
        file_r = '../html/templates/auction_notice.html'
        file_w = '../html/{}/{}/{}/{}/{}'.format(case['province'], case['city'], case['districtName'],
                                                 case['categoryName'], case['caseId'])
        file_w = os.path.join(file_w, 'auction_notice.html')
        with open(file_r, 'r', encoding='utf-8') as fr:
            with open(file_w, 'w', encoding='utf-8') as fw:
                ret = fr.read()
                # 填充模板
                title = '竞买' if '拍卖' in case['caseStatus'] else '应买'
                ret = ret.format(title, case['auctionNotice'])
                fw.write(ret)


def auction_instruction(case, func_li):
    """
    竞买/应买须知
    :param case: 案例对象
    :param func_li: 函数名列表
    :return: None
    """
    func_name = sys._getframe().f_code.co_name
    if func_name in func_li:
        file_r = '../html/templates/auction_instruction.html'
        file_w = '../html/{}/{}/{}/{}/{}'.format(case['province'], case['city'], case['districtName'],
                                                 case['categoryName'], case['caseId'])
        file_w = os.path.join(file_w, 'auction_instruction.html')
        with open(file_r, 'r', encoding='utf-8') as fr:
            with open(file_w, 'w', encoding='utf-8') as fw:
                ret = fr.read()
                # 填充模板
                title = '竞买' if '拍卖' in case['caseStatus'] else '应买'
                ret = ret.format(title, case['auctionInstruction'])
                fw.write(ret)


def description(case, func_li):
    """
    标的物介绍
    :param case: 案例对象
    :param func_li: 函数名列表
    :return: None
    """
    regex_1 = re.compile(r'<table style="(.*?)"', re.S)
    regex_2 = re.compile(r'<div class="slide-bigpic"><img.*?></div>', re.S)
    regex_3 = re.compile(r'标的物调查情况表', re.S)
    func_name = sys._getframe().f_code.co_name
    if func_name in func_li:
        file_r = '../html/templates/description.html'
        file_w = '../html/{}/{}/{}/{}/{}'.format(case['province'], case['city'], case['districtName'],
                                                 case['categoryName'], case['caseId'])
        file_w = os.path.join(file_w, 'description.html')
        with open(file_r, 'r', encoding='utf-8') as fr:
            with open(file_w, 'w', encoding='utf-8') as fw:
                ret = fr.read()
                # 清洗文字
                case['description'] = regex_3.sub('', case['description'])
                # 填充模板
                ret = ret.format(case['description'])
                # 表格居中
                ret_li_1 = regex_1.findall(ret)
                sub_str = ret_li_1[0] + 'margin:0 auto;'
                ret = re.sub(ret_li_1[0], sub_str, ret)
                # 删除图片
                ret_li_2 = regex_2.findall(ret)
                ret_li_2.insert(0, ret)
                ret = reduce(lambda x, y: re.sub(y, '', x), ret_li_2) if len(ret_li_2) > 1 else ret
                fw.write(ret)


def transfer_date(stamp):
    """
    将时间戳转换为date
    :param stamp: 13位时间戳
    :return: tuple
    """
    date_obj = datetime.datetime.fromtimestamp(int(stamp) / 1000, None)
    date_str_1 = date_obj.strftime("%Y/%m/%d %H:%M:%S")
    date_str_2 = date_str_1.split(' ')[0]
    date_str_2 = date_str_2.replace('/', '年', 1).replace('/', '月', 1) + '日'
    return date_str_1, date_str_2


def purchase_confirm(case, func_li):
    """
    竞价成功确认书
    :param case: 案例对象
    :param func_li: 函数名列表
    :return: None
    """
    regex_date = re.compile(r'display:none')
    func_name = sys._getframe().f_code.co_name
    if func_name in func_li:
        file_r = '../html/templates/purchase_confirm.html'
        file_w = '../html/{}/{}/{}/{}/{}'.format(case['province'], case['city'], case['districtName'],
                                                 case['categoryName'], case['caseId'])
        file_w = os.path.join(file_w, 'purchase_confirm.html')
        confirm_dict = case['purchaseConfirm']
        court_name = confirm_dict['courtName']
        auction_title = confirm_dict['auctionTitle']
        detail_url = confirm_dict['detailUrl']
        notice_time = confirm_dict['noticeTime']
        auction_start_time = confirm_dict['auctionStartTime']
        auction_end_time = confirm_dict['auctionEndTime']
        last_time = confirm_dict['lastTime']
        buyer_name = confirm_dict['buyerName']
        buyer_alias_name = confirm_dict['buyerAliasName']
        price_cent = int(confirm_dict['priceCent']) // 100
        dtb = DigitToRmb(price_cent)
        price_dtb = dtb.main()
        del dtb
        with open(file_r, 'r', encoding='utf-8') as fr:
            with open(file_w, 'w', encoding='utf-8') as fw:
                ret = fr.read()
                if auction_end_time != last_time:
                    ret = regex_date.sub('', ret)
                # 时间格式转换
                notice_time = transfer_date(notice_time)[0]
                auction_start_time = transfer_date(auction_start_time)[0]
                auction_end_time = transfer_date(auction_end_time)
                last_time = transfer_date(last_time)[1]
                # 填充模板
                ret = ret.format(court_name, auction_title, detail_url, notice_time, auction_start_time,
                                 auction_end_time[0], buyer_name, buyer_alias_name, auction_end_time[1], court_name,
                                 auction_title, price_cent, price_dtb, court_name, last_time, court_name, last_time)
                fw.write(ret)


def bid_records(case, func_li):
    """
    竞买/应买记录
    :param case: 案例对象
    :param func_li: 函数名列表
    :return: None
    """
    func_name = sys._getframe().f_code.co_name
    if func_name in func_li:
        file_r = '../html/templates/bid_records.html'
        file_w = '../html/{}/{}/{}/{}/{}'.format(case['province'], case['city'], case['districtName'],
                                                 case['categoryName'], case['caseId'])
        file_w = os.path.join(file_w, 'bid_records.html')
        with open(file_r, 'r', encoding='utf-8') as fr:
            with open(file_w, 'w', encoding='utf-8') as fw:
                ret = fr.read()
                # 填充模板
                title = '竞买' if '拍卖' in case['caseStatus'] else '应买'
                tr_li = case['bidRecords']
                tr_str = ''
                for i, tr_dict in enumerate(tr_li):
                    tr_str += TR_GET_STR.format(tr_dict['alias'], tr_dict['price'],
                                                tr_dict['date']) if i == 0 else TR_OUT_STR.format(tr_dict['alias'],
                                                                                                  tr_dict['price'],
                                                                                                  tr_dict['date'])
                ret = ret.format(title, title, tr_str)
                fw.write(ret)


def get_cases_li(col, query, skip_num):
    """
    获取案例列表
    :param col: 集合对象
    :param skip_num: 开始查询数
    :return: list
    """
    # cases_cursor = col.find({'purchaseConfirm': {'$ne': None}}).skip(skip_num).limit(2000)
    cases_cursor = col.find(query).skip(skip_num).limit(2000)
    cases_li = list(cases_cursor)
    return cases_li


def get_func_li(case):
    """
    获取函数名列表
    :param case: 案例对象
    :return: list
    """
    func_li = list()
    func_li.append('auction_notice') if case['auctionNotice'] and not case['auctionNotice'].startswith('http') else 1
    func_li.append('auction_instruction') if case['auctionInstruction'] and not case['auctionInstruction'].startswith(
        'http') else 2
    func_li.append('description') if case['description'] and not case['description'].startswith('http') else 3
    func_li.append('purchase_confirm') if isinstance(case['purchaseConfirm'], dict) else 4
    func_li.append('bid_records') if isinstance(case['bidRecords'], list) else 5
    return func_li


def main(host=HOST, port=PORT):
    """
    主函数
    :param host: '127.0.0.1'
    :param port: 27017
    :return: None
    """
    cli = MongoClient(host, port)
    col = cli['sfpm']['case']
    skip_num = 0
    while True:
        cases_li = get_cases_li(col, dict(), skip_num)
        if cases_li:
            skip_num += 2000
            for case in cases_li:
                file_path = '../html/{}/{}/{}/{}/{}'.format(case['province'], case['city'], case['districtName'],
                                                            case['categoryName'], case['caseId'])
                if not os.path.exists(file_path):
                    os.makedirs(file_path)
                    func_li = get_func_li(case)
                    task_li = [EXECUTOR.submit(eval(func), case, func_li) for func in func_li]
                    wait(task_li)
                else:
                    continue
            # break  # 仅测试用，正式环境需注释或删除
        else:
            break
    cli.close()


if __name__ == '__main__':
    main()